package org.testis.testdriver.parser;

import org.testis.data.parser.AtofModuleParameterNames;
import org.testis.orm.testbed.refined.DeviceGroupDetailRefined;
import org.testis.orm.testbed.refined.DeviceGroupFactory;
import org.testis.orm.testbed.refined.DeviceGroupRefined;
import org.testis.orm.testbed.refined.DutRefined;
import org.testis.orm.testbed.refined.TestPcFactory;
import org.testis.orm.testbed.refined.TestPcRefined;
import org.testis.testdriver.AtofEnumaration;
import org.testis.testdriver.ITestBuilder;
import org.testis.testdriver.TestPlanBuilder;
import org.testis.testdriver.TestPlanGlobalsHashMap;
import java.util.HashMap;
import java.util.LinkedList;
import org.orm.PersistentException;
import org.testis.orm.classes.T_bed_directserialconfig;
import org.testis.orm.classes.T_bed_directserialconfigCriteria;
import org.testis.orm.classes.T_bed_networkserialconfiguration;
import org.testis.orm.classes.T_bed_networkserialconfigurationCriteria;
import org.testis.orm.refinedclasses.TestDesignTreeNode;
import org.testis.orm.refinedclasses.TestPlanRefined;
import org.testis.orm.refinedclasses.TestDesignTreeRefined.TestDesignTreeParameters;
import org.testis.utils.middleware.GlobalDataHandler;
import org.testis.utils.middleware.LanguageDataHandler;

/**
 *
 * @author barisergun
 */
public class TestDriverTestPlanRefinedParsing extends TestDriverAbstractParsingStrategy {

    public TestDriverTestPlanRefinedParsing(ITestBuilder builder,
            TestDesignTreeNode currentNode) {
        m_builder = builder;
        m_currentNode = currentNode;

        if (m_currentNode.isClone()) {
            m_cloneString = " [clone]";
        }
    }

    @Override
    public void parseCurrentNode() throws PersistentException {
        String deviceIpInTestPlan = null;

        String deviceIp = m_currentNode.getReference().getParameterStringValue(TestDesignTreeParameters.DeviceIp.name());
        Integer deviceId = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.DeviceId.name());
        String browserType = m_currentNode.getReference().getParameterStringValue(TestDesignTreeParameters.BrowserType.name());
        Integer browserSpeed = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.BrowserSpeed.name());
        Integer pcId = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.PcId.name());
        DutRefined device = null;
        TestPcRefined pc = null;
        if (pcId != null) {
            pc = TestPcFactory.newInstance().getTestPc(pcId);
        }
        if (deviceId != null && pc != null) {
            device = pc.getDut(deviceId);
        }

        Integer testBedId = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.TestBedId.name());
        Integer languageId = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.LanguageId.name());
        Integer profileId = m_currentNode.getReference().getParameterIntValue(TestDesignTreeParameters.ProfileId.name());

        LinkedList<String> condList = getConditionsOfTestPart();

        if (deviceIp == null
                || deviceIp.equals("")) {
            deviceIpInTestPlan = getFactoryIpFromDeviceId(String.valueOf(
                    deviceId));
        } else {
            deviceIpInTestPlan = deviceIp;
        }

        TestPlanRefined testPart =
                (TestPlanRefined) m_currentNode.getObject();
        m_builder.buildTestPart(String.valueOf(m_currentNode.getId()),
                testPart.getName() + m_cloneString,
                testPart.getReference().getDescription(),
                AtofEnumaration.TestPartType.TestPlan,
                String.valueOf(m_currentNode.getParent().getId()));
        m_builder.setTestPlanDutRunTime(String.valueOf(m_currentNode.getId()),
                device.getActiveFirmware().getName(),
                String.valueOf(deviceId),
                browserType,
                browserSpeed,
                deviceIpInTestPlan,
                device.getTestBedIp());

        m_builder.setTestPartConditions(String.valueOf(m_currentNode.getId()), condList);

        String atofVersion = "N/A";
        try {
            atofVersion = java.lang.Package.getPackage(
                    "org.testis.client").getImplementationVersion()
                    + "." + java.lang.Package.getPackage("org.testis.client").
                    getSpecificationVersion();
        } catch (Exception ex) {
        }
        if (testBedId != null && device.getPc() != null) {
            DeviceGroupRefined testBed = DeviceGroupFactory.newInstance().getDeviceGroup(testBedId);
            DeviceGroupDetailRefined pcItem = testBed.getDetailByPcId(pc.getId());
            String testPcMac = pcItem.getMacAddress();
            if (testPcMac != null) {
                m_builder.setTestPlanTestPcRunTime(String.valueOf(m_currentNode.getId()),
                        atofVersion,
                        testPcMac);
            } else if (m_builder instanceof TestPlanBuilder) {
                ((TestPlanBuilder) m_builder).pushExceptionMessage(
                        "Test PC does not exist in the given test bed..."
                        + " at TestPlan Problem Node:"
                        + getCurrentNodePath());
            }

        } else {
            if (m_builder instanceof TestPlanBuilder) {
                ((TestPlanBuilder) m_builder).pushExceptionMessage(
                        "Test PC must be selected"
                        + " at TestPlan Problem Node:"
                        + getCurrentNodePath());
            }
        }



        TestPlanGlobalsHashMap.createInstance().resetMaps();
        LanguageDataHandler langHandler = new LanguageDataHandler();
        GlobalDataHandler globalHandler = new GlobalDataHandler();

        if (languageId != null) {
            HashMap<String, String> langMap = langHandler.getLanguagePairsAsMap(
                    languageId);

            if (langMap != null) {
                TestPlanGlobalsHashMap.createInstance().putAllLangValues(
                        langMap);
            }
        } else {
            if (m_builder instanceof TestPlanBuilder) {
                ((TestPlanBuilder) m_builder).pushExceptionMessage(
                        "DUT Language must be selected"
                        + " at TestPlan. Problem Node:"
                        + getCurrentNodePath());
            }

        }

        if (profileId != null) {
            HashMap<String, String> globalMap = globalHandler.getProfileDetailsAsMap(
                    profileId);


            if (globalMap != null) {
                TestPlanGlobalsHashMap.createInstance().putAllGlobalsValues(
                        globalMap);
            }
        } else {

            if (m_builder instanceof TestPlanBuilder) {
                ((TestPlanBuilder) m_builder).pushExceptionMessage(
                        "Profile for Globals must be selected"
                        + " at TestPlan Problem Node:"
                        + getCurrentNodePath());
            }

        }

        m_builder.setTestPlanGlobals(String.valueOf(m_currentNode.getId()),
                languageId,
                profileId);



        if (device != null) {

            HashMap<String, String> dutValues = new HashMap<String, String>();
            String testBedIp = device.getTestBedIp();

            if (testBedIp != null) {
                dutValues.put(AtofModuleParameterNames.DUT_TEST_BED_IP,
                        device.getTestBedIp());

            } else {
                if (m_builder instanceof TestPlanBuilder) {
                    ((TestPlanBuilder) m_builder).pushExceptionMessage(
                            "Test Bed Ip was not set in Test Bed for this DUT"
                            + " at TestPlan Problem Node:"
                            + getCurrentNodePath());
                }
            }
            String testFactoryIp = getFactoryIpFromDeviceId(String.valueOf(
                    device.getId()));
            if (testFactoryIp != null) {
                dutValues.put(AtofModuleParameterNames.DUT_FACTORY_IP,
                        testFactoryIp);
            } else {
                if (m_builder instanceof TestPlanBuilder) {
                    ((TestPlanBuilder) m_builder).pushExceptionMessage(
                            "DUT Factory Ip was not set in Test Bed for this DUT"
                            + " at TestPlan Problem Node:"
                            + getCurrentNodePath());
                }
            }

            if (dutValues != null) {
                TestPlanGlobalsHashMap.createInstance().putAllDutValues(
                        dutValues);
            }

        } else {
            if (m_builder instanceof TestPlanBuilder) {
                ((TestPlanBuilder) m_builder).pushExceptionMessage(
                        "DUT must be selected"
                        + " at TestPlan Problem Node:"
                        + getCurrentNodePath());
            }
        }


        if (device.getIsSerialActive()) {
            HashMap<String, String> serialParams = new HashMap<String, String>();
            int connId = device.getSerialConnection().getConfigId();

            String connTypeName = device.getSerialConnection().getConnectType().getName();

            if ((connTypeName.equals("direct"))) {
                T_bed_directserialconfigCriteria criter =
                        new T_bed_directserialconfigCriteria();
                criter.id.eq(connId);
                T_bed_directserialconfig serialConfs = criter.uniqueT_bed_directserialconfig();

                serialParams.put(AtofModuleParameterNames.SPM_COM_PORT_NO,
                        String.valueOf(serialConfs.getPort()));
                serialParams.put(AtofModuleParameterNames.SPM_BAUD_RATE,
                        serialConfs.getBoundary());
                serialParams.put(AtofModuleParameterNames.SPM_STOP_BITS,
                        String.valueOf(serialConfs.getStopBit()));
                serialParams.put(AtofModuleParameterNames.SPM_FLOW_CONTROL,
                        String.valueOf(serialConfs.getFlowControl()));
                serialParams.put(AtofModuleParameterNames.SPM_PARITY,
                        String.valueOf(serialConfs.getParity()));
                serialParams.put(AtofModuleParameterNames.SPM_DATA_BITS,
                        String.valueOf(serialConfs.getDataBit()));
                serialParams.put(AtofModuleParameterNames.SPM_CONFIG_NAME,
                        serialConfs.getConfigName());

            } else if (connTypeName.equals("network")) {

                T_bed_networkserialconfigurationCriteria criter =
                        new T_bed_networkserialconfigurationCriteria();
                criter.id.eq(connId);
                T_bed_networkserialconfiguration serialConfs = criter.uniqueT_bed_networkserialconfiguration();

                serialParams.put(AtofModuleParameterNames.SPM_CONFIG_NAME,
                        serialConfs.getConfigName());
                serialParams.put(AtofModuleParameterNames.SPM_NETWORK_IP,
                        serialConfs.getIp());
                serialParams.put(AtofModuleParameterNames.SPM_NETWORK_PORT,
                        serialConfs.getPort());


            }

            m_builder.setTestPlanDutSerial(String.valueOf(m_currentNode.getId()),
                    serialParams);


        }
    }
}
